# Draw two little squares inside of a square as part of the same path,
# then fill it.  The square at the bottom of the page is filled with the
# default filling method.  You'll see that the inner square marked CCW
# (means it was traversed in the counterclockwise direction) is filled,
# but the CW sqare is not.   The upper square on the page is filled with
# a different PostScript filling method called eofill, or "even-odd"
# fill. 
# 
# See the documentation for an explanation of the difference between the
# fillPath() and the eofillPath() commands.
#
###########################################################################

from g import *
from versiondec import VersionDec as vd
import random

# Set the following variable to nonzero if you want to send the generated
# files directly to a PostScript printer.  Otherwise, set it to zero.

wrap_in_PJL = 0

rand = random.random   # Convenience name for a random number generator that 
                       # returns a uniformly-distributed random number between
                       # 0.0 and 1.0.

def SetUp(file, orientation=portrait, units=inches):
    '''Convenience function to set up the drawing environment and return a
    file object to the output stream.
    '''
    ofp = open(file, "w")
    ginitialize(ofp, wrap_in_PJL)
    setOrientation(orientation, units)
    return ofp

def ShowDifferentFillTypes(file):
    s = SetUp(file, portrait, inches)
    textName(Sans)
    lineWidth(.03)
    newPath()
    fill_color   = yellow
    border_color = navy
 
    # Draw some lines to show the background
    push()
    lineColor(red)
    lineWidth(.01)
    translate(.75, 0)
    for ix in range(15):
        move(0, 0)
        rline(4, 4)
        translate(0, .5)
    pop()
 
    # Make a big square; add points counterclockwise
    pathAddPoint(1, 1)
    pathAddPoint(4, 1)
    pathAddPoint(4, 4)
    pathAddPoint(1, 4)
    pathClose()
 
    # Make two smaller squares; add points clockwise and counterclockwise
    ll    = 1.5
    delta = 1
    pathAddPoint(ll+delta, ll)
    pathAddPoint(ll, ll)
    pathAddPoint(ll, ll+delta)
    pathAddPoint(ll+delta, ll+delta)
    pathClose()
 
    ll    = 2.5
    pathAddPoint(ll, ll)
    pathAddPoint(ll+delta, ll)
    pathAddPoint(ll+delta, ll+delta)
    pathAddPoint(ll, ll+delta)
    pathClose()
 
    p = getPath()
 
    # Fill the path
    fillOn()
    fillColor(fill_color)
    fillPath()
    # Draw a border
    setPath(p)
    lineColor(border_color)
    drawPath()
 
    # Label the inner squares 
    textSize(.3)
    move(1.7, 1.9)
    text("CW")
    move(2.65, 2.9)
    text("CCW")
    # Label the fill type
    move(5, 2.5)
    text("non-zero winding fill")
    move(5, 2.2)
    text("(default)")
 
    # Move to a location above the squares just drawn, redraw the path,
    # and use eofillPath() this time.
    translate(0, 5)
    setPath(p)
    fillColor(fill_color)
    eofillPath()
    # Draw a border
    setPath(p)
    lineColor(border_color)
    drawPath()
 
    # Label the inner squares 
    textSize(.3)
    move(1.7, 1.9)
    text("CW")
    move(2.65, 2.9)
    text("CCW")
    move(5, 2.5)
    text("eofill")
 
    # Put some explanation at the top
    translate(0, 4.2)
    move(0, 0)
    fillColor(white)
    fillOn()
    lineOff()
    rectangle(8.5, 2)
 
    translate(.5, 0)   # Left margin
    move(0, 1.3)
    textSize(.2)
    text("This demonstrates the differences between two PostScript filling methods.")
    move(0, 1.1)
    text("eofill is even-odd fill:  an area is filled if a line from inside to infinity crosses an odd")
    move(0, .9)
    text("number of lines.  The default fill is non-zero winding, in which the direction of the ")
    move(0, .7)
    text("lines crossed is included in the sum.")
 
    s.close()

ShowDifferentFillTypes(vd("out/fill_eofill.ps"))
